package com.g7.figmaapi.common.exception.handle;

import com.alibaba.fastjson.JSONObject;
import com.g7.figmaapi.common.result.WebResult;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.core.annotation.AnnotationUtils;
import org.springframework.http.HttpStatus;
import org.springframework.web.bind.annotation.ResponseStatus;
import org.springframework.web.servlet.ModelAndView;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;

/**
 * @author: taoxiangqian
 * @explain: 全局基础异常处理类
 * @since: 2023/10/26 10:24
 */
public class BaseGlobalExceptionHandler {
    private static final Logger logger = LoggerFactory.getLogger(BaseGlobalExceptionHandler.class);

    public BaseGlobalExceptionHandler() {
    }

    protected ModelAndView handleError(HttpServletRequest req, HttpServletResponse rsp, Exception e, String errorName, HttpStatus status) throws Exception {
        if (AnnotationUtils.findAnnotation(e.getClass(), ResponseStatus.class) != null) {
            throw e;
        } else {
            WebResult exceptionMsg = ExceptionUtil.getExceptionMsg(req, e);
            if (StringUtils.isNotBlank(errorName) && !isAjax(req)) {
                return handleViewError(req.getRequestURL().toString(), exceptionMsg, errorName);
            } else {
                handleAjaxError(rsp, JSONObject.toJSONString(exceptionMsg), status);
                return null;
            }
        }
    }

    protected ModelAndView handleViewError(String url, WebResult exceptionMsg, String viewName) {
        ModelAndView mav = new ModelAndView();
        mav.addObject("url", url);
        String v = "redirect:";
        if (viewName.indexOf(v) < 0) {
            mav.addObject("code", exceptionMsg.getCode());
            mav.addObject("exception", exceptionMsg.getException());
            mav.addObject("msg", exceptionMsg.getMsg());
            mav.addObject("timestamp", exceptionMsg.getTimestamp());
        }

        mav.setViewName(viewName);
        return mav;
    }

    protected ModelAndView handleAjaxError(HttpServletResponse rsp, String errorMessage, HttpStatus status) throws IOException {
        rsp.setCharacterEncoding("UTF-8");
        rsp.setStatus(status.value());
        rsp.setContentType("application/json; charset=utf-8");
        PrintWriter writer = rsp.getWriter();
        writer.write(errorMessage);
        writer.flush();
        writer.close();
        return null;
    }

    boolean isAjax(HttpServletRequest request) {
        String accept = request.getHeader("accept");
        String contentType = request.getHeader("content-type");
        String xRequestedWith = request.getHeader("X-Requested-With");
        return (accept != null && accept.contains("application/json"))
                || (contentType != null && contentType.contains("application/json"))
                || (xRequestedWith != null && xRequestedWith.contains("XMLHttpRequest"));
    }
}
